package config

import (
	goscanmgt "goscan-mgt"
	"log"
	"os"
	"path/filepath"
	"sync"

	"github.com/spf13/viper"
)

type DatabaseConfig struct {
	Type string
	Path string
}

type LoggingConfig struct {
	Enabled bool
	Format  string
	Level   string
	File    string
}

type Config struct {
	Port    int
	DB      DatabaseConfig
	Logging LoggingConfig
}

var (
	cfg  *Config
	once sync.Once
)

func ensureConfigFile() error {
	exePath, err := os.Executable()
	if err != nil {
		return err
	}
	dir := filepath.Dir(exePath)
	configDir := filepath.Join(dir, "config")
	if _, err := os.Stat(configDir); os.IsNotExist(err) {
		if err := os.MkdirAll(configDir, 0755); err != nil {
			return err
		}
	}
	configPath := filepath.Join(configDir, "config.yaml")
	if _, err := os.Stat(configPath); os.IsNotExist(err) {
		if err := os.WriteFile(configPath, goscanmgt.DefaultConfig, 0644); err != nil {
			return err
		}
	}
	return nil
}

func LoadConfig() *Config {
	once.Do(func() {
		if err := ensureConfigFile(); err != nil {
			log.Fatalf("自动释放配置文件失败: %v", err)
		}
		viper.SetConfigName("config")
		viper.SetConfigType("yaml")
		viper.AddConfigPath("./config")
		if err := viper.ReadInConfig(); err != nil {
			log.Fatalf("读取配置文件失败: %v", err)
		}
		cfg = &Config{
			Port: viper.GetInt("port"),
			DB: DatabaseConfig{
				Type: viper.GetString("DB.type"),
				Path: viper.GetString("DB.path"),
			},
			Logging: LoggingConfig{
				Enabled: viper.GetBool("logging.enabled"),
				Format:  viper.GetString("logging.format"),
				Level:   viper.GetString("logging.level"),
				File:    viper.GetString("logging.file"),
			},
		}
	})
	return cfg
}
